package hongcheng.code_generator.templet.freemarker;

import java.io.File;
import java.io.IOException;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.io.IORuntimeException;
import cn.hutool.core.util.ClassUtil;
import cn.hutool.extra.template.engine.freemarker.SimpleStringTemplateLoader;
import freemarker.cache.ClassTemplateLoader;
import freemarker.cache.FileTemplateLoader;
import freemarker.template.Configuration;
import freemarker.template.TemplateExceptionHandler;
import hongcheng.code_generator.entity.config.CodeGeneratorConfig;
import hongcheng.code_generator.entity.config.TempletFileConfig.ResourceMode;
import hongcheng.code_generator.exception.CustomException;
import hongcheng.code_generator.templet.ITemplet;
import hongcheng.code_generator.templet.AbstractTempletManager;


/**
 * freemarker模板引擎管理器
 */
public class FreemarkerManager extends AbstractTempletManager{

	

	/**
	 * 	构造函数
	 * 	@param config 配置文件信息
	 * */
	public FreemarkerManager(CodeGeneratorConfig configParam) {
		super(configParam);
	}



	/**
	 * 	获取controller模板类
	 * */
	@Override
	public ITemplet getControllerTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getControllerTplPath(), config.getTplConfig().getControllerTplResourceMode());
	}

	/**
	 * 	获取Service模板类
	 * */
	@Override
	public ITemplet getServiceTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getServiceTplPath(), config.getTplConfig().getServiceTplResourceMode());
	}

	/**
	 * 	获取ServiceImpl模板类
	 * */
	@Override
	public ITemplet getServiceImplTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getServiceImplTplPath(), config.getTplConfig().getServiceImplTplResourceMode());
	}

	/**
	 * 	获取Dao模板类
	 * */
	@Override
	public ITemplet getDaoTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getDaoTplPath(), config.getTplConfig().getDaoTplResourceMode());
	}

	/**
	 * 	获取Entity模板类
	 * */
	@Override
	public ITemplet getEntityTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getEntityTplPath(), config.getTplConfig().getEntityTplResourceMode());
	}

	/**
	 * 	获取QueryVO模板类
	 * */
	@Override
	public ITemplet getQueryvOTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getQueryVOTplPath(), config.getTplConfig().getQueryVOTplResourceMode());
	}

	/**
	 * 	获取xml模板类
	 * */
	@Override
	public ITemplet getXMLTemplet() {
		CodeGeneratorConfig config = getConfig();
		return this.getConfiguration(config.getTplConfig().getXmlTplPath(), config.getTplConfig().getXmlTplResourceMode());
	}

	
	
	/***
	 * 	获取FreemarkerTemplet模板类
	 * 	@param templetFilePath 模板文件地址  <br>
	 * 	@param resourceMode 文件地址类型  <br>
	 * 			如果是 CLASSPATH 或 WEB_ROOT ，则 templetFilePath 必须是相对路径<br>
	 * 			如果是 FILE  ，则 templetFilePath 必须是绝对路径<br>
	 * */
	private FreemarkerTemplet getConfiguration(String templetFilePath,ResourceMode resourceMode) {
		Configuration controllerConfiguration = new Configuration(Configuration.VERSION_2_3_29);
		controllerConfiguration.setDefaultEncoding("UTF-8");
		controllerConfiguration.setTemplateExceptionHandler(TemplateExceptionHandler.RETHROW_HANDLER);
		controllerConfiguration.setLocalizedLookup(false);
		
		switch (resourceMode) {
			case CLASSPATH:
				// 注意：basePackagePath必须是相对路径，他会自己拼接上classpath的，如果是绝对路径会报错
				controllerConfiguration.setTemplateLoader(new ClassTemplateLoader(ClassUtil.getClassLoader()
						, new File(templetFilePath).getParent()));
				break;
			case FILE:
				try {
					controllerConfiguration.setTemplateLoader(new FileTemplateLoader(FileUtil.getParent(new File(templetFilePath),1)));
				} catch (IOException e) {
					throw new IORuntimeException(e);
				}
				break;
			case WEB_ROOT:
				 try {
					 controllerConfiguration.setTemplateLoader(new FileTemplateLoader(FileUtil.file(FileUtil.getWebRoot()
							 , new File(templetFilePath).getParent())));
				 } catch (IOException e) {
					 throw new IORuntimeException(e);
				 }
				break;
			case STRING:
				controllerConfiguration.setTemplateLoader(new SimpleStringTemplateLoader());
				break;
			default:
				throw new CustomException("{}模板来源只能是CLASSPATH、FILE、WEB_ROOT、STRING",templetFilePath);
		}
		return new FreemarkerTemplet(controllerConfiguration,new File(templetFilePath).getName());
	}
	
	


	

	
	
	
	
	
	
	
}
